package serializer

import (
	"QImages/utils"
	"github.com/gin-gonic/gin"
)

// Response 基础序列化器
type Response struct {
	Code int `json:"code"`
	// omitempty 表示为空则不输出
	Data      interface{} `json:"data,omitempty"`
	Msg       string      `json:"msg"`
	Error     string      `json:"error,omitempty"`
	Timestamp string      `json:"timestamp"`
}

// TrackedErrorResponse 有追踪信息的错误响应
type TrackedErrorResponse struct {
	Response
	TrackID string `json:"track_id"`
}

// 三位数错误编码为复用http原本含义
// 五位数错误编码为应用自定义错误
// 五开头的五位数错误编码为服务器端错误，比如数据库操作失败
// 四开头的五位数错误编码为客户端错误，有时候是客户端代码写错了，有时候是用户操作错误
const (
	// CodeCheckLogin 未登录
	CodeCheckLogin = 401
	//CodeParamErr 各种奇奇怪怪的参数错误
	CodeParamErr = 40001
	// CodeNothingFound 未找到数据
	CodeNothingFound = 40002
	// CodeForbidden 未授权访问
	CodeForbidden = 40003
	// CodeLoginFailed 登录失败
	CodeLoginFailed = 40004
	// CodeUserExist 用户名已存在
	CodeUserExist = 40005
	// CodeDBError 数据库操作失败
	CodeDBError = 50001
	// CodeEncryptError 加密失败
	CodeEncryptError = 50002
	// CodeServerError 服务端出现的错误总称
	CodeServerError = 50003
)

// CheckLogin 检查登录
func CheckLogin() Response {
	return Response{
		Code: CodeCheckLogin,
		Msg:  "未登录",
	}
}

// Err 通用错误处理
func Err(errCode int, msg string, err error) Response {
	res := Response{
		Code:      errCode,
		Msg:       msg,
		Timestamp: utils.Now(),
	}
	// 生产环境隐藏底层报错
	if err != nil && gin.Mode() != gin.ReleaseMode {
		res.Error = err.Error()
	}
	return res
}

// DBErr 数据库操作失败
func DBErr(msg string, err error) Response {
	if msg == "" {
		msg = "数据库操作失败"
	}
	return Err(CodeDBError, msg, err)
}

// ParamErr 各种参数错误
func ParamErr(msg string, err error) Response {
	if msg == "" {
		msg = "参数错误"
	}
	return Err(CodeParamErr, msg, err)
}

// ServerErr 服务端错误的统称
func ServerErr(msg string, err error) Response {
	if msg == "" {
		msg = "出现错误"
	}
	return Err(CodeServerError, msg, err)
}

//OK 操作成功
func OK(msg string, data interface{}) Response {
	if msg == "" {
		msg = "操作成功"
	}
	return Response{
		Msg:       msg,
		Data:      data,
		Timestamp: utils.Now(),
	}
}
